﻿using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Linq;
using System.Text;

using ESRI.ArcGIS.esriSystem;
using ESRI.ArcGIS.Geodatabase;
using esriGeodatabase = ESRI.ArcGIS.Geodatabase;
using System.Windows.Forms; 

namespace EngineWindowsApplication1.SDESqlServerConnect
{
    internal class SqlServerConnectInfor
    {
        #region 连接常量

        private const String SERVER = "PC-201203161034";//服务器名称
        private const String INSTANCE = "esri_sde";//服务名称
        private const String DATABASE = "sde";//数据库名称
        private const String USER = "sde";//用户
        private const String PASSWORD = "222222";//密码
        private const String VERSION = "sde.DEFAULT";//版本
        #endregion


        // 连接SQL Server 的连接字符串
        private const String CONNECT_STRING_FORMAT = "SERVER={0};INSTANCE={1};DATABASE={2};USER={3};PASSWORD={4};VERSION={5}";

        // SdeWorkspaceFactory 对象的ProgID
        private const String SDE_WorkspaceFactory_ProgID  = "esriDataSourcesGDB.SdeWorkspaceFactory";

        private readonly string _server;//服务器名称
        private readonly string _instance;//服务名称
        private readonly string _user;//用户
        private readonly string _password;//密码
        private readonly string _database;//数据库名称
        private readonly string _version;//版本

        private readonly string _connectString;//连接字符串

        private readonly IWorkspaceFactory2 _workspaceFactory;//生产Workspace
        private IWorkspace _workspace;
        private IFeatureWorkspace _featureWorkspace = null;

        private readonly List<IDatasetName> _datasetNameList = new List<IDatasetName>();//dataset名称列表



        /// <summary>
        /// 构造函数
        /// </summary>
        /// <param name="server">服务器名称</param>
        /// <param name="instance">服务名称</param>
        /// <param name="database">数据库名</param>
        /// <param name="user">用户</param>
        /// <param name="password">密码</param>
        /// <param name="version">版本</param>
        internal SqlServerConnectInfor(String server, String instance, String database, String user, String password, String version)
        {
            _server = server;
            _instance = instance;
            _database = database;
            _user = user;
            _password = password;
            _version = version;

            //生成连接字符串
            _connectString = String.Format(CONNECT_STRING_FORMAT,_server,_instance,_database,_user,_password,_version);

            //得到sde工厂
            _workspaceFactory =(IWorkspaceFactory2) Activator.CreateInstance(Type.GetTypeFromProgID(SDE_WorkspaceFactory_ProgID));
        }


        /// <summary>
        /// 获取连接字符串
        /// </summary>
        /// <returns></returns>
        internal String GetConnectString()
        {
            return this._connectString;
        }



        /// <summary>
        /// 尝试连接
        /// </summary>
        /// <returns>错误信息</returns>
        internal String TryToConnect()
        {
            //如果不为空
            if (null != _workspace) return string.Empty;

            try
            {
                _workspace = _workspaceFactory.OpenFromString(_connectString, 0);//字符串连接
                //_workspace = _workspaceFactory.OpenFromString(string.Empty, 0);//字符串连接
                _featureWorkspace = (IFeatureWorkspace)_workspace;
            }
            catch (COMException comEx)
            {
                return comEx.Message;
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
            catch {
                return "连接数据库时发生未知错误！";
            }
            return String.Empty;
        }



        /// <summary>
        /// 获取数据库工作空间
        /// </summary>
        /// <returns></returns>
        internal IWorkspace GetWorkspace()
        {
            if (null != _workspace)
            {
                return _workspace;
            }
            else
            {
                String err = this.TryToConnect();
                if (!String.IsNullOrEmpty(err)) // 发生错误
                {
                    MessageBox.Show(err,"错误",MessageBoxButtons.OK,MessageBoxIcon.Information);
                }
                return _workspace;
            }
        }


        /// <summary>
        /// 获取dataset名称列表
        /// </summary>
        /// <param name="refresh">是否刷新</param>
        /// <returns></returns>
        internal List<IDatasetName> GetDatasetNames(Boolean refresh)
        {
            if (!refresh)
            {
                this.Getdfsf();
            }
            return _datasetNameList;
        }


        /// <summary>
        /// 
        /// </summary>
        internal void Getdfsf()
        {
            //获取datasetName（不区分类型）
            IEnumDatasetName enumDatasetName = _workspace.get_DatasetNames(esriDatasetType.esriDTAny);

            enumDatasetName.Reset();

            IDatasetName datasetName = null;

            _datasetNameList.Clear();

            //遍历dataset
            while ((datasetName = enumDatasetName.Next()) != null)
            {
                _datasetNameList.Add(datasetName);

                //判断dataset的类型
                switch (datasetName.Type)
                {
                    case esriDatasetType.esriDTFeatureDataset:
                        break;
                    default: 
                        break;
                }

                //如果是feature dataset
                if (datasetName.Type == esriDatasetType.esriDTFeatureDataset)
                {
                    IFeatureDatasetName2 featureDatasetName2 = (IFeatureDatasetName2)datasetName;
                    IEnumDatasetName enumDatasetName1 = featureDatasetName2.FeatureClassNames;//所有要素类的枚举
                    IDatasetName datasetName1 = null;//featureclass 也是 dataset
                    while ((datasetName1 = enumDatasetName1.Next()) != null)
                    {
                        _datasetNameList.Add(datasetName1);
                    }

                    #region 其他如：TableNames、TopologyNames,RelationshipClassNames,GeometricNetworkNames

                    IEnumDatasetName enumDatasetName2 = featureDatasetName2.TableNames;//表名
                    IDatasetName datasetName2 = null;
                    while ((datasetName2 = enumDatasetName2.Next()) != null)
                    {
                        _datasetNameList.Add(datasetName2);
                    }

                    IEnumDatasetName enumDatasetName3 = featureDatasetName2.TopologyNames;//拓扑名
                    IDatasetName datasetName3 = null;
                    while ((datasetName3 = enumDatasetName2.Next()) != null)
                    {
                        _datasetNameList.Add(datasetName3);
                    }


                    IEnumDatasetName enumDatasetName4 = featureDatasetName2.RelationshipClassNames;//有关系的类名
                    IDatasetName datasetName4 = null;
                    while ((datasetName4 = enumDatasetName2.Next()) != null)
                    {
                        _datasetNameList.Add(datasetName4);
                    }

                    IEnumDatasetName enumDatasetName5 = featureDatasetName2.GeometricNetworkNames;//几何网络名
                    IDatasetName datasetName5= null;
                    while ((datasetName5 = enumDatasetName2.Next()) != null)
                    {
                        _datasetNameList.Add(datasetName5);
                    }
                    #endregion
                }
            }
        }


    }
}
